package com.crazymakercircle.mutithread.basic.create;

import lombok.extern.slf4j.Slf4j;

import java.util.concurrent.atomic.AtomicInteger;

import static com.crazymakercircle.util.ThreadUtil.sleepMilliSeconds;

/**
 * Created by 尼恩@疯狂创客圈.
 */
@Slf4j
public class SalesDemo {
    public static final int MAX_AMOUNT = 100; //商品数量

    public static void main(String[] args) throws InterruptedException {
        /*log.info("商店版本的销售");
        for (int i = 1; i <= 2; i++) {
            Thread thread = null;
            thread = new StoreGoods1("店员-" + i);
            thread.start();
        }

        log.info("商店版本的销售");
        for (int i = 1; i <= 2; i++) {
            Thread thread = null;
            thread = new StoreGoods2("xx-" + i);
            thread.start();
        }

        Thread.sleep(1000);*/
        log.info("商场的商品销售");
        MallGoods mallGoods = new MallGoods();
        for (int i = 1; i <= 2; i++) {
            Thread thread = null;
            thread = new Thread(mallGoods, "商场销售员-" + i);
            thread.start();
        }
        log.info("运行结束。");
    }

    //商店商品的销售线程，每条线程异步销售4次
    static class StoreGoods1 extends Thread {
        // 这个要看每个线程是不是共卖一份还是自己卖自己的
        // 如果是static就是共卖一份，大家卖一份就需要注意线程安全问题
        // 如果不是的话，就是自己卖自己的，互不影响

        // 这里是自己卖自己的
        private int goodsAmount = MAX_AMOUNT;

        StoreGoods1(String name) {
            super(name);
        }

        public void run() {
            for (int i = 0; i <= MAX_AMOUNT; i++) {
                if (this.goodsAmount > 0) {
                    log.info("卖出一件，还剩：{}", (--goodsAmount));
                    sleepMilliSeconds(10);
                }
            }
            log.info("运行结束。");
        }
    }

    static class StoreGoods2 extends Thread {
        //        private static int goodsAmount = MAX_AMOUNT;
        private static Integer goodsAmount = MAX_AMOUNT;

        StoreGoods2(String name) {
            super(name);
        }

        public void run() {
            for (int i = 0; i <= MAX_AMOUNT; i++) {
                synchronized (goodsAmount) {
                    if (goodsAmount > 0) {
                        log.info(" 卖出一件，还剩：{}", (--goodsAmount));
                        sleepMilliSeconds(10);
                    }
                }
            }
            log.info("运行结束。");
        }
    }

    //商场商品的target销售目标类，一个商品最多销售4次，可以多人销售
    static class MallGoods implements Runnable {
        //多人销售, 可能导致数据出错，使用原子数据类型保障数据安全
        private final AtomicInteger goodsAmount = new AtomicInteger(MAX_AMOUNT);

        public void run() {
            for (int i = 0; i <= MAX_AMOUNT; i++) {
                if (this.goodsAmount.get() > 0) {
                    log.info("卖出一件，还剩：{}", (goodsAmount.decrementAndGet()));
                    sleepMilliSeconds(10);
                }
            }
            log.info("运行结束。");
        }
    }
}